/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
package wargame.controller;

import java.util.ArrayList;
import java.util.Timer;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import module.GameTurn;
import module.GenerateCompany;
import module.GenerateProject;
import module.GlobalConstant;
import module.ManageEmployee;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.servlet.ModelAndView;
import wargame.dao.BidDAO;
import wargame.dao.CompanyDAO;
import wargame.dao.EconomicDAO;
import wargame.dao.EmployeeDAO;
import wargame.dao.GameLogDAO;
import wargame.dao.NotificationDAO;
import wargame.dao.OutsourceProjectDAO;
import wargame.dao.PlayerDAO;
import wargame.dao.ProjectDAO;
import wargame.dao.ProjectInjectDAO;
import wargame.dao.TransactionDAO;
import wargame.entity.Company;
import wargame.entity.Economic;
import wargame.entity.Player;
import wargame.entity.Project;
import wargame.entity.ProjectInject;
import wargame.entity.TurnTask;

/**
 *
 * @author Clarence
 */
@Controller
@RequestMapping(value = "/admin")
public class AdminController {

    private static TurnTask turnTask = new TurnTask();

    @RequestMapping(value = "/panel", method = RequestMethod.GET)
    public ModelAndView adminPanel(@RequestParam(value = "announcement", required = false) String announcement,
            Model model) {
        ModelAndView mv = new ModelAndView();

        ArrayList<Player> player_list = PlayerDAO.retrieveAllPlayers();

        for (Player player : player_list) {
            ArrayList<Project> project_list = ProjectDAO.retrievePlayerProjects(player.getPlayer_id());
            for (Project project : project_list) {
                ProjectInject inject = ProjectInjectDAO.findForTurn(project.getProject_id(), GameTurn.current_turn + 1);
                if (inject != null) {
                    project.setInject(inject);
                }
            }
            player.setPlayer_project(project_list);
        }

        mv.setViewName("admin");
        mv.addObject("turn", GameTurn.getTurnInfo());
        mv.addObject("player_list", player_list);
        if (announcement != null) {
            mv.addObject("announcement", announcement);
        }

        return mv;
    }

    @RequestMapping(value = "/startGame", method = RequestMethod.POST)
    public ModelAndView startGame(
            //@RequestParam(value = "start_game", required = true) String start_game,
            HttpServletRequest request, HttpServletResponse response, Model model) {

        ModelAndView mv = new ModelAndView();
        String announcement = "";
        if (GameTurn.current_turn < 0) {

            start(false);

            announcement = "Successfully start game!";
        } else {
            announcement = "Game is already started!";
        }

        mv.setViewName("redirect:/servlet/admin/panel");
        mv.addObject("announcement", announcement);

        return mv;
    }

    @RequestMapping(value = "/reStartGame", method = RequestMethod.POST)
    public ModelAndView reStartGame(
            //@RequestParam(value = "start_game", required = true) String start_game,
            HttpServletRequest request, HttpServletResponse response, Model model) {

        ModelAndView mv = new ModelAndView();
        String announcement = "";

        start(true);

        announcement = "Successfully reStart game!";


        mv.setViewName("redirect:/servlet/admin/panel");
        mv.addObject("announcement", announcement);

        return mv;

    }

    private static void start(boolean restart) {
        // set the game turn settings
        GameTurn.current_turn = 0;
        GameTurn.game_pause = false;
        if (!restart) {
            GameTurn.timer = new Timer();
        }
        GameTurn.elapsed_second = 0;
        GameTurn.turn_length = GlobalConstant.FIVE_MIN;

        // clear the company, employee, temp_employee, project, outsource_project table
        CompanyDAO.clear();
        EmployeeDAO.clear();
        EmployeeDAO.clear_temp();
        ProjectDAO.clear();
        OutsourceProjectDAO.clear();
        BidDAO.clear();
        EconomicDAO.clear();
        NotificationDAO.clear();
        PlayerDAO.clear();
        ProjectDAO.clear_assign_project();
        GameLogDAO.clear();
        TransactionDAO.clear();

        //generate employees
        ManageEmployee.autoGenEmployee();

        //generate companies
        GenerateCompany.generateCompany("NCS Pte Ltd");
        GenerateCompany.generateCompany("IBM");
        GenerateCompany.generateCompany("Microsoft");
        GenerateCompany.generateCompany("Google");
        GenerateCompany.generateCompany("Barclays");

        //generate project
        ArrayList<Player> playerlist = PlayerDAO.retrieveAllPlayers();
        ArrayList<Company> companyList = CompanyDAO.retrieveAll();

        Economic economicIndex = new Economic();
        economicIndex.setEconomic_index(10.0);
        economicIndex.setTurn(0);
        EconomicDAO.insertEconomic(economicIndex);
        GameTurn.index = 10.0;

        int projectFactor = (playerlist.size() / companyList.size()) + 1;

        for (int i = 0; i < projectFactor; i++) {
            for (Company company : companyList) {
                GenerateProject.createProject(company, GameTurn.current_turn);
            }
        }
        int delay = 0; // delay start for 0 sec.
        int period = 1000; // repeat every sec.

        // set the timer
        if (!restart) {
            GameTurn.timer.scheduleAtFixedRate(turnTask, delay, period);
        }
    }

    @RequestMapping(value = "/nextTurn", method = RequestMethod.POST)
    public ModelAndView nextTurn(
            // @RequestParam(value = "next_turn", required = true) String next_turn,
            HttpServletRequest request, HttpServletResponse response, Model model) {

        ModelAndView mv = new ModelAndView();

        GameTurn.turn_length = GameTurn.elapsed_second;

        mv.setViewName("redirect:/servlet/admin/panel");
        mv.addObject("announcement", "Next turn started!");

        return mv;

    }

    @RequestMapping(value = "/pauseGame", method = RequestMethod.POST)
    public ModelAndView pauseGame(
            //            @RequestParam(value = "pause_game", required = true) String pause_game,
            HttpServletRequest request, HttpServletResponse response, Model model) {

        ModelAndView mv = new ModelAndView();

        GameTurn.game_pause = !GameTurn.game_pause;

        String announcement = (GameTurn.game_pause) ? "Game Paused!" : "Game Resumed!";

        mv.setViewName("redirect:/servlet/admin/panel");
        mv.addObject("announcement", announcement);

        return mv;
    }

    @RequestMapping(value = "/endGame", method = RequestMethod.POST)
    public ModelAndView endGame(
            //            @RequestParam(value = "pause_game", required = true) String pause_game,
            HttpServletRequest request, HttpServletResponse response, Model model) {

        ModelAndView mv = new ModelAndView();

        GameTurn.game_pause = true;
        GameTurn.current_turn = GlobalConstant.END_GAME;
        String announcement = "game ended";

        mv.setViewName("redirect:/servlet/admin/panel");
        mv.addObject("announcement", announcement);

        return mv;
    }

    @RequestMapping(value = "/project/{project_id}/inject", method = RequestMethod.POST)
    public ModelAndView injectProjectScope(@PathVariable("project_id") int project_id,
            HttpServletRequest request, HttpServletResponse response, Model model,
            @RequestParam(value = "dot_net", required = false) Integer dot_net,
            @RequestParam(value = "c_sharp", required = false) Integer c_sharp,
            @RequestParam(value = "jsp", required = false) Integer jsp,
            @RequestParam(value = "php", required = false) Integer php,
            @RequestParam(value = "ruby", required = false) Integer ruby,
            @RequestParam(value = "mysql", required = false) Integer mysql,
            @RequestParam(value = "mssql", required = false) Integer mssql,
            @RequestParam(value = "oracle", required = false) Integer oracle,
            @RequestParam(value = "price", required = true) Integer price) {

        ModelAndView mv = new ModelAndView();
        String announcement = "";

        ProjectInject projectInject = new ProjectInject();
        projectInject.setProject_id(project_id);
        projectInject.setDot_net(dot_net);
        projectInject.setC_sharp(c_sharp);
        projectInject.setJsp(jsp);
        projectInject.setPhp(php);
        projectInject.setRuby(ruby);
        projectInject.setMysql(mysql);
        projectInject.setMssql(mssql);
        projectInject.setOracle(oracle);
        projectInject.setPrice(price);
        projectInject.setTurn(GameTurn.current_turn + 1);

        ProjectInjectDAO.insert(projectInject);

        announcement = "successfully inserted injects for project id #" + project_id;

        mv.setViewName("redirect:/servlet/admin/panel");
        mv.addObject("announcement", announcement);

        return mv;
    }

    @RequestMapping(value = "/project/{project_id}/update_inject", method = RequestMethod.POST)
    public ModelAndView updateProjectScope(@PathVariable("project_id") int project_id,
            HttpServletRequest request, HttpServletResponse response, Model model,
            @RequestParam(value = "dot_net", required = false) Integer dot_net,
            @RequestParam(value = "c_sharp", required = false) Integer c_sharp,
            @RequestParam(value = "jsp", required = false) Integer jsp,
            @RequestParam(value = "php", required = false) Integer php,
            @RequestParam(value = "ruby", required = false) Integer ruby,
            @RequestParam(value = "mysql", required = false) Integer mysql,
            @RequestParam(value = "mssql", required = false) Integer mssql,
            @RequestParam(value = "oracle", required = false) Integer oracle,
            @RequestParam(value = "price", required = true) Integer price) {

        ModelAndView mv = new ModelAndView();
        String announcement = "";

        ProjectInject projectInject = new ProjectInject();
        projectInject.setProject_id(project_id);
        projectInject.setDot_net(dot_net);
        projectInject.setC_sharp(c_sharp);
        projectInject.setJsp(jsp);
        projectInject.setPhp(php);
        projectInject.setRuby(ruby);
        projectInject.setMysql(mysql);
        projectInject.setMssql(mssql);
        projectInject.setOracle(oracle);
        projectInject.setPrice(price);
        projectInject.setTurn(GameTurn.current_turn + 1);

        ProjectInjectDAO.update(projectInject);

        announcement = "successfully updated injects for project id #" + project_id;

        mv.setViewName("redirect:/servlet/admin/panel");
        mv.addObject("announcement", announcement);

        return mv;
    }

    @RequestMapping(value = "/project/{project_id}/delete_inject", method = RequestMethod.GET)
    public ModelAndView deleteProjectScope(@PathVariable("project_id") int project_id,
            HttpServletRequest request, HttpServletResponse response, Model model) {

        ModelAndView mv = new ModelAndView();
        String announcement = "";

        ProjectInjectDAO.delete(project_id);

        announcement = "successfully deleted injects for project id #" + project_id;

        mv.setViewName("redirect:/servlet/admin/panel");
        mv.addObject("announcement", announcement);

        return mv;
    }

    @RequestMapping(value = "/update_index", method = RequestMethod.POST)
    public ModelAndView updateIndex(@RequestParam(value = "index") Double index,
            HttpServletRequest request, HttpServletResponse response, Model model) {

        ModelAndView mv = new ModelAndView();
        String announcement = "";

        GameTurn.index = index;

        announcement = "successfully updated next turn economic index";

        mv.setViewName("redirect:/servlet/admin/panel");
        mv.addObject("announcement", announcement);

        return mv;
    }
}
